use crate::models::response::{Response as ErrorResponse, ResponseFailed};
use axum::{http::StatusCode, response::IntoResponse, Json};
use thiserror::Error;
#[derive(Debug, Error)]
pub enum AppError {
    #[error("io Error: {0}")]
    IoError(#[from] std::io::Error),

    #[error("sqlx Error: {0}")]
    SqlxError(#[from] sqlx::Error),
    #[error("json Error: {0}")]
    UserNotFound(String),
    #[error("general Error: {0}")]
    AnyError(#[from] anyhow::Error),
    #[error(" Error:")]
    UserAlreadyExists,
    #[error(" argon2 hash password Error:{0}")]
    Argon2HashError(#[from] argon2::password_hash::Error),
}

impl IntoResponse for AppError {
    fn into_response(self) -> axum::response::Response {
        let (status, error_message) = match self {
            Self::IoError(_) => (StatusCode::INTERNAL_SERVER_ERROR, "IO error occurred"),
            Self::SqlxError(_) => (StatusCode::INTERNAL_SERVER_ERROR, "Database error occurred"),
            Self::AnyError(_) => (StatusCode::INTERNAL_SERVER_ERROR, "General error occurred"),
            Self::UserAlreadyExists => (StatusCode::BAD_REQUEST, "User already exists"),
            Self::Argon2HashError(_) => (
                StatusCode::INTERNAL_SERVER_ERROR,
                "Argon2 hash password error occurred",
            ),
            Self::UserNotFound(_) => {
                // 直接使用 msg 的值，避免借用临时值
                (StatusCode::NOT_FOUND, "Not Found")
            }
        };
        let response = ErrorResponse::<String>::failed(status.as_u16(), error_message.to_string());
        // 调整为正确的调用方式
        Json(response).into_response()
    }
}
